package net.chasing.androidbaseconfig.widget.arrow;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Path;
import androidx.annotation.Nullable;
import android.util.AttributeSet;
import android.view.View;

import net.chasing.androidbaseconfig.R;

public class ArrowView extends View {
    private static final int CIRCLE_SIZE = 10; //顶角圆形长间距

    private int mArrowWidth = 0, mArrowHeight = 0, mBackgroundColor = 0xf8f8f8;
    private Paint mPaint;
    private Path mPath;
    private byte mOrientation = ORIENTATION_UP;
    private boolean isCircle; //顶角是否是圆形

    public static final byte ORIENTATION_UP = 0;
    public static final byte ORIENTATION_DOWN = 1;
    public static final byte ORIENTATION_LEFT = 2;
    public static final byte ORIENTATION_RIGHT = 3;

    public static final byte ORIENTATION_LEFT_TOP = 4;

    public ArrowView(Context context) {
        this(context, null);
    }

    public ArrowView(Context context, @Nullable AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public ArrowView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init(context, attrs, defStyleAttr);
    }

    private void init(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        if (attrs != null) {
            TypedArray a = context.getTheme().obtainStyledAttributes(attrs,
                    R.styleable.ArrowView, defStyleAttr, 0);
            int attr;
            for (int i = 0; i < a.getIndexCount(); i++) {
                attr = a.getIndex(i);
                if (attr == R.styleable.ArrowView_background_color) {
                    mBackgroundColor = a.getColor(attr, 0xf8f8f8);
                } else if (attr == R.styleable.ArrowView_arrow_orientation) {
                    mOrientation = (byte) a.getInt(attr, ORIENTATION_UP);
                } else if (attr == R.styleable.ArrowView_is_circle) {
                    isCircle = a.getBoolean(attr, false);
                }
            }
            a.recycle();
        }
    }

    public void setOrientation(byte orientation) {
        mOrientation = orientation;
        if (mArrowWidth > 0 && mArrowHeight > 0) {
            createPath();
        }
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        if (mArrowWidth == 0 || mArrowHeight == 0) {
            mArrowWidth = getMeasuredWidth();
            mArrowHeight = getMeasuredHeight();

            mPaint = new Paint();
            mPaint.setAntiAlias(true);
            mPaint.setColor(mBackgroundColor);
            mPaint.setStyle(Paint.Style.FILL);

            createPath();
        }
    }

    private void createPath() {
        mPath = new Path();
        int circleWidth, circleHeight;
        if (mOrientation == ORIENTATION_UP) {
            mPath.moveTo(0, mArrowHeight);
            if (isCircle) {
                circleHeight = CIRCLE_SIZE;
                circleWidth = (int) (mArrowWidth / 2f * circleHeight / mArrowHeight);
                mPath.lineTo(mArrowWidth / 2f - circleWidth, circleHeight);
                mPath.quadTo(mArrowWidth / 2f, 0,
                        mArrowWidth / 2f + circleWidth, circleHeight);
            } else
                mPath.lineTo(mArrowWidth / 2f, 0);
            mPath.lineTo(mArrowWidth, mArrowHeight);
        } else if (mOrientation == ORIENTATION_DOWN) {
            mPath.moveTo(0, 0);
            if (isCircle) {
                circleHeight = CIRCLE_SIZE;
                circleWidth = (int) (mArrowWidth / 2f * circleHeight / mArrowHeight);
                mPath.lineTo(mArrowWidth / 2f - circleWidth, mArrowHeight - circleHeight);
                mPath.quadTo(mArrowWidth / 2f, mArrowHeight,
                        mArrowWidth / 2f + circleWidth, mArrowHeight - circleHeight);
            } else
                mPath.lineTo(mArrowWidth / 2f, mArrowHeight);
            mPath.lineTo(mArrowWidth, 0);
        } else if (mOrientation == ORIENTATION_LEFT) {
            mPath.moveTo(mArrowWidth, 0);
            if (isCircle) {
                circleWidth = CIRCLE_SIZE;
                circleHeight = (int) (mArrowHeight / 2f * circleWidth / mArrowWidth);
                mPath.lineTo(circleWidth, mArrowHeight / 2f - circleHeight);
                mPath.quadTo(0, mArrowHeight / 2f,
                        circleWidth, mArrowHeight / 2f + circleHeight);
            } else
                mPath.lineTo(0, mArrowHeight / 2f);
            mPath.lineTo(mArrowWidth, mArrowHeight);
        } else if (mOrientation == ORIENTATION_RIGHT) {
            mPath.moveTo(0, 0);
            if (isCircle) {
                circleWidth = CIRCLE_SIZE;
                circleHeight = (int) (mArrowHeight / 2f * circleWidth / mArrowWidth);
                mPath.lineTo(mArrowWidth - circleWidth, mArrowHeight / 2f - circleHeight);
                mPath.quadTo(mArrowWidth, mArrowHeight / 2f,
                        mArrowWidth - circleWidth, mArrowHeight / 2f + circleHeight);
            } else
                mPath.lineTo(mArrowWidth, mArrowHeight / 2f);
            mPath.lineTo(0, mArrowHeight);
        } else if (mOrientation == ORIENTATION_LEFT_TOP){
            mPath.moveTo(0, 0);
            mPath.lineTo(mArrowWidth, 0);
            mPath.lineTo(0, mArrowHeight);
        }
        mPath.close();
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        if (mPaint != null && mPath != null)
            canvas.drawPath(mPath, mPaint);
    }
}
